<template>
    <div>
        <div class="container">
            <div class="uploadBox">
                <el-upload
                    v-bind="action"
                    :before-upload="handleBeforeUpload"
                    :file-list="fileList"
                    :limit="uploadConfig.limit"
                    :data="uploadConfig.params"
                    :on-error="handleUploadError"
                    :on-exceed="handleExceed"
                    :on-success="handleUploadSuccess"
                    :on-change="handleChange"
                    :on-remove="handleDelete"
                    :on-preview="handlePreview"
                    :headers="uploadConfig.headers"
                    :auto-upload="false"
                    class="upload-file-uploader"
                    ref="upload"
                    drag
                    :multiple="uploadConfig.multiple"
                    :accept="accept"
                >
                    <div class="content">
                        <i class="el-icon-plus"></i>
                        <div class="text">上传文件</div>
                    </div>

                    <div class="el-upload__tip" slot="tip" v-if="showTip">
                        <slot name="tip">
                            <div class="tip">
                                <div class="section">
                                    请上传
                                    <template v-if="uploadConfig.fileSize">
                                        大小不超过
                                        <b style="color: #f56c6c"
                                            >{{ uploadConfig.fileSize }}MB</b
                                        >的
                                    </template>
                                    文件
                                    <span
                                        v-if="uploadConfig.templateUrl"
                                        style="display: flex"
                                        >，<span
                                            @click="downloadTemplate"
                                            class="downloadTemplate"
                                        >
                                            请先下载模板
                                        </span>
                                    </span>
                                </div>
                                <div v-if="uploadConfig.fileType">
                                    格式为
                                    <b style="color: #f56c6c">{{
                                        uploadConfig.fileType.join("/")
                                    }}</b>
                                </div>
                                <div v-html="uploadConfig.tip"></div>
                            </div>
                        </slot>
                    </div>
                    <div slot="file" slot-scope="{ file }">
                        <div class="file">
                            <i class="el-icon-paperclip icon"></i>
                            <div class="text">
                                <TooltipDiv :content="file.name"></TooltipDiv>
                            </div>
                            <i
                                class="el-icon-delete delete"
                                @click="handle_delete(file)"
                            ></i>
                        </div>
                    </div>
                </el-upload>
            </div>
        </div>
    </div>
</template>
<script>
import TooltipDiv from "@/views/quota/forecast/chunk/tooltipDiv";
import request from "@/utils/request";
export default {
    name: "",
    components: { TooltipDiv },
    props: {
        uploadConfig: {
            type: Object,
            default: () => ({}),
        },
        isShowTip: {
            type: Boolean,
            default: true,
        },
        params: {
            type: Object,
            default: () => ({}),
        },
    },
    data() {
        return {
            url: "",
            fileList: [],
            fileListLength: 0,
            uploadFilesResult: {
                errorMsg: "",
                success: [],
                error: [],
                state: "",
                filelist: [],
                info: {},
                data: {},
            },
            customUploading: false,
        };
    },

    computed: {
        // 是否显示提示
        showTip() {
            return (
                this.isShowTip &&
                (this.uploadConfig.fileType || this.uploadConfig.fileSize)
            );
        },
        accept() {
            let fileTypes = this.uploadConfig?.fileType?.map((item) => {
                return `.${item}`;
            });
            return fileTypes?.join(",");
        },
        action() {
            let reg = /^#.*/g;
            let isCustom = reg.test(this.uploadConfig.uploadFileUrl);
            let url = process.env.VUE_APP_BASE_API;

            if (isCustom) {
                this.url = this.uploadConfig.uploadFileUrl.slice(1);
            } else {
                this.url += this.uploadConfig.uploadFileUrl;
            }
            let config = {
                action: isCustom ? "#" : this.url,
                httpRequest: this.handle_upload,
            };
            if (!isCustom) {
                delete config.httpRequest;
            }
            return config;
        },
    },

    mounted() {
        this.refRedirect.call(this, "upload");
    },
    methods: {
        downloadTemplate() {
            if (this.uploadConfig.templateUrl) {
                this.download_get(
                    this.uploadConfig.templateUrl,
                    {},
                    `${this.uploadConfig.templateName}`
                );
            }
        },
        handle_upload(file) {
            if (this.customUploading || this.fileList?.length == 0) return;
            let params = new FormData();

            for (const [key, value] of Object.entries(
                this.uploadConfig.params
            )) {
                params.append(key, value);
            }

            for (const [key, value] of Object.entries(this.fileList)) {
                params.append(`file`, value.raw);
            }
            this.customUploading = true;

            let config = {};
            if (this.uploadConfig.method == "get") {
                config.params = params;
            } else if (this.uploadConfig.method == "post") {
                config.data = params;
            }

            request({
                url: this.url,
                method: this.uploadConfig.method,
                ...config,
            })
                .then((res) => {
                    if (res.code == 200) {
                        this.uploadFilesResult.info.success =
                            res?.data?.successCount;
                        this.uploadFilesResult.info.error =
                            res?.data?.errorCount;
                        this.uploadFilesResult.data =
                            res.rows ?? res?.data?.resultList;
                        if (res?.data?.errorCount > 0) {
                            this.$message.error("导入失败！");
                        } else {
                            this.$message({
                                message: "导入成功！",
                                type: "success",
                            });
                        }
                        this.uploadFilesResult.errUrl = res?.data?.errUrl
                    } else {
                        throw new Error(res.msg);
                    }
                })
                .catch((err) => {
                    console.log(err);
                    this.$message.error("导入失败！");
                    this.uploadFilesResult.errorMsg = err;
                })
                .finally(() => {
                    this.customUploading = false;
                    this.changeStep();
                });
        },
        uploadEnd(response) {
            this.$emit("uploadEnd", this.uploadFilesResult);
        },
        handle_delete(file) {
            let index = this.fileList.findIndex((item) => {
                file.uid == item.uid;
            });
            this.fileList.splice(index, 1);
        },
        initUpload() {
            this.fileList = [];
            this.fileListLength = 0;
            this.uploadFilesResult = {
                success: [],
                error: [],
                state: "",
                filelist: [],
                info: {},
                data: {},
            };
            this.$nextTick(() => {
                this.$refs.upload?.clearFiles();
            });
        },
        // 判断是否全部上传完毕
        checkFilesState() {
            let afterUpload =
                this.fileList.length > 0 &&
                this.fileList.reduce((prev, next) => {
                    return prev && "state" in next && next.status !== "ready";
                }, true);
            if (afterUpload) {
                this.changeStep();
            }
        },
        // 文件全部上传完毕
        changeStep() {
            this.uploadFilesResult.success = [];
            this.uploadFilesResult.error = [];
            // this.uploadFilesResult.filelist = this.fileList;
            // this.fileList.map((item) => {
            //     if (item.state == "success") {
            //         this.uploadFilesResult.success.push(item);
            //     }
            //     if (item.state == "error") {
            //         this.uploadFilesResult.error.push(item);
            //     }
            // });

            if (
                this.uploadFilesResult.error?.length > 0 ||
                this.uploadFilesResult?.info?.error > 0
            ) {
                this.uploadFilesResult.state = "error";
            } else {
                this.uploadFilesResult.state = "success";
            }
            this.$emit("uploadEnd", this.uploadFilesResult);
        },

        handlePreview(file) {
            let url = URL.createObjectURL(file.raw);
            this._previewImages([url]);
        },
        handleChange(file, fileList) {
            if (fileList.length > this.fileListLength) {
                // 新增
                let pass = this.lintFile(file);
                if (!pass) {
                    let index = fileList.findIndex(
                        (item) => item.uid === file.uid
                    );
                    fileList.splice(index, 1);
                }
                this.fileList = fileList;
                this.fileListLength = fileList.length;
            }
            this.checkFilesState();
        },

        handleRemove(file) {
            // console.log(file);
        },

        handleDownload(file) {
            // console.log(file);
        },
        // 上传前校检格式和大小
        handleBeforeUpload(file) {
            let pass = true;
            pass = this.lintFile(file);
            return pass;
        },
        lintFile(file) {
            // 校检文件类型
            if (this.uploadConfig.fileType) {
                const fileName = file.name.split(".");
                const fileExt = fileName[fileName.length - 1];
                const isTypeOk =
                    this.uploadConfig.fileType.indexOf(fileExt) >= 0;
                if (!isTypeOk) {
                    this.$modal.msgError(
                        `文件格式不正确, 请上传${this.uploadConfig.fileType.join(
                            "/"
                        )}格式文件!`
                    );
                    return false;
                }
            }
            // 校检文件大小
            if (this.uploadConfig.fileSize) {
                const isLt =
                    file.size / 1024 / 1024 < this.uploadConfig.fileSize;
                if (!isLt) {
                    this.$modal.msgError(
                        `上传文件大小不能超过 ${this.uploadConfig.fileSize} MB!`
                    );
                    return false;
                }
            }
            return true;
        },
        // 文件个数超出
        handleExceed(files, fileList) {
            if (this.uploadConfig.limit !== 1) {
                this.$modal.msgError(
                    `上传文件数量不能超过 ${this.uploadConfig.limit} 个!`
                );
            } else {
                let file = files[files.length - 1];
                file.uid = new Date().getTime();
                let obj = {
                    name: file.name,
                    percentage: 0,
                    raw: file,
                    size: file.size,
                    status: "ready",
                    // uid: new Date().getTime(),
                    uid: file.uid,
                };
                this.fileList = [obj];
            }
        },
        // 上传失败
        handleUploadError(err, file, fileList) {
            console.log("error");
            let item = this.fileList.find((item) => item.uid === file.uid);
            if (item) {
                item.state = "error";
            }
            this.fileList = fileList;
            this.fileList.push(item);
            this.$modal.closeLoading();
            this.$nextTick(() => {
                this.$modal.msgError("上传文件失败，请重试");
            });
        },
        // 上传成功回调
        handleUploadSuccess(res, file, fileList) {
            let item = fileList.find((item) => item.uid === file.uid);
            item.name = res.data.fileName;
            item.url = res.data.url;
            item.ossId = res.data.ossId;
            if (res.code === 200) {
                item.state = "success";
            } else {
                this.$modal.msgError(res.msg);
                item.state = "error";
            }
            // this.uploadedSuccessfully();
            this.fileList = fileList;
        },
        // 删除文件
        handleDelete(file, filelist) {
            let index = this.fileList.findIndex((item) => {
                return item.uid == file.uid;
            });
            if (file.status !== "ready") {
                let item = this.fileList.find((e) => {
                    return e.uid == file.uid;
                });
                // if (item?.ossId) {
                //     delOss(item.ossId);
                // }
                this.fileList.splice(index, 1);
            } else {
                this.fileList = filelist;
                this.fileListLength = this.fileList.length;
            }
        },
        // 上传结束处理
        uploadedSuccessfully() {},
        // 获取文件名称
        getFileName(name) {
            // 如果是url那么取最后的名字 如果不是直接返回
            if (name.lastIndexOf("/") > -1) {
                return name.slice(name.lastIndexOf("/") + 1);
            } else {
                return name;
            }
        },
        // 对象转成指定字符串分隔
        listToString(list, separator) {
            let strs = "";
            separator = separator || ",";
            for (let i in list) {
                strs += list[i].ossId + separator;
            }
            return strs != "" ? strs.substr(0, strs.length - 1) : "";
        },
    },
};
</script>
<style lang="scss" scoped>
.container {
    // width: 300px;
    background: #fff;
    display: flex;
    justify-content: center;
    padding: 20px 0;
}
.tips {
    align-self: flex-start;
}
.uploadBox {
    width: 440px;
    display: flex;
    flex-direction: column;
    justify-content: center;
    align-items: center;
}
.content {
    height: 100%;
    border: 1px dashed #d9d9d9;
    display: flex;
    flex-direction: column;
    justify-content: center;
    align-items: center;
    .text {
        font-size: 16px;
        color: #606266;
        margin-top: 10px;
    }
}
::v-deep .upload-file-uploader {
    display: flex;
    flex-direction: column;
    .el-upload {
        margin: 0 auto;
    }
}
::v-deep .el-upload-dragger {
    width: 240px;
    height: 120px;
}
::v-deep .el-upload__tip {
    width: 260px;
    margin: 0 auto;
}
.tip {
    margin-top: 15px;
    font-family: PingFangSC, PingFang SC;
    font-weight: 400;
    font-size: 12px;
    color: #333333;
    line-height: 20px;
    text-align: left;
    font-style: normal;
    .section {
        display: flex;
        flex-wrap: wrap;
        overflow-wrap: break-word;
        word-wrap: break-word;
        word-break: break-all;
        ::v-deep .el-button {
            padding: 0;
        }
    }
}

.file {
    display: flex;

    font-family: PingFangSC, PingFang SC;
    font-weight: 400;
    font-size: 14px;
    color: #333333;
    line-height: 22px;
    text-align: left;
    font-style: normal;
    align-items: center;
    .icon {
        margin-right: 15px;
    }
    .text {
        flex: 1;
        min-width: 0;
    }
    .delete {
        margin-left: 15px;
        cursor: pointer;
    }
}
::v-deep .el-upload-list {
    width: 260px;
    margin-top: 15px;
    max-height: 120px;
    overflow-y: overlay;
    display: flex;
    flex-direction: column;
    gap: 5px 0;
    padding-right: 10px;
    box-sizing: border-box;
    .el-upload-list__item {
        margin: 0;
    }
}
.downloadTemplate {
    display: flex;
    color: #1890ff;
    cursor: pointer;
}
</style>
